package br.com.massai.model.entity;

import java.io.Serializable;
import java.util.ArrayList;
import java.util.List;

import javax.persistence.CascadeType;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.EnumType;
import javax.persistence.Enumerated;
import javax.persistence.FetchType;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.JoinColumn;
import javax.persistence.JoinTable;
import javax.persistence.ManyToMany;
import javax.persistence.ManyToOne;
import javax.persistence.NamedQueries;
import javax.persistence.NamedQuery;
import javax.persistence.SequenceGenerator;
import javax.persistence.Table;
import javax.persistence.Transient;

import org.hibernate.annotations.Fetch;
import org.hibernate.annotations.FetchMode;

import br.com.massai.view.enums.StatusObraEnum;

@Entity
@Table(name = "OBRA", schema = "PORTAL")
@SequenceGenerator(name = "seqObra", sequenceName = "seq_obra", allocationSize = 1)
@NamedQueries({
		@NamedQuery(name = "Obra.findAll", query = "SELECT o FROM Obra o"), 
		@NamedQuery(name = "Obra.duplicata", query = "SELECT o FROM Obra o WHERE o.codigoColigada = :coligada AND o.codigoDepto = :depto AND o.codigoSienge = :sienge AND o.id <> :id")
})
public class Obra implements Serializable {

	private static final long serialVersionUID = 2180202261621875322L;

	@Id
	@Column(name = "ID_OBRA")
	@GeneratedValue(generator = "seqObra", strategy = GenerationType.SEQUENCE)
	private Long id;

	@Column(name = "CODIGO_COLIGADA")
	private Long codigoColigada;

	@Column(name = "CODIGO_DEPTO", nullable = false, columnDefinition = "VARCHAR(15)")
	private String codigoDepto;

	@Column(name = "CODIGO_SIENGE")
	private Long codigoSienge;

	@Column(name = "NOME", nullable = false, columnDefinition = "VARCHAR(255)")
	private String nome;

	@Column(name = "NOME_FANTASIA", nullable = false, columnDefinition = "VARCHAR(255)")
	private String nomeFantasia;

	@Enumerated(EnumType.STRING)
	@Column(name = "ATIVO", nullable = false, columnDefinition = "CHAR")
	private StatusObraEnum status;

	@ManyToOne(optional = true, fetch = FetchType.LAZY, cascade = CascadeType.MERGE)
	@JoinColumn(referencedColumnName = "ID_GRUPO_PRODUCAO", name = "ID_GRUPO_PRODUCAO")
	private GrupoProducao grupoProducao;

	@ManyToMany(fetch = FetchType.LAZY, cascade = CascadeType.MERGE)
	@Fetch(FetchMode.SUBSELECT)
	@JoinTable(name = "COLABORADORES", 
		joinColumns = @JoinColumn(name = "ID_OBRA", referencedColumnName = "ID_OBRA"), 
		inverseJoinColumns = @JoinColumn(name = "ID_USUARIO", referencedColumnName = "ID_USUARIO"))
	private List<Usuario> listaUsuarios;

	@Transient
	private boolean select;

	public Obra() {
		this.listaUsuarios = new ArrayList<Usuario>();
	}

	@Override
	public boolean equals(Object obj) {
		if(obj == null) return false;
		if(obj instanceof Obra)
			if(((Obra) obj).getId().equals(this.getId())) return true;
		return false;
	}

	public Long getId() {
		return id;
	}

	public void setId(Long id) {
		this.id = id;
	}

	public GrupoProducao getGrupoProducao() {
		return grupoProducao;
	}

	public void setGrupoProducao(GrupoProducao grupoProducao) {
		this.grupoProducao = grupoProducao;
	}

	public String getNome() {
		return nome;
	}

	public void setNome(String nome) {
		this.nome = nome;
	}

	public String getNomeFantasia() {
		return nomeFantasia;
	}

	public void setNomeFantasia(String nomeFantasia) {
		this.nomeFantasia = nomeFantasia;
	}

	public StatusObraEnum getStatus() {
		return status;
	}

	public void setStatus(StatusObraEnum status) {
		this.status = status;
	}

	public boolean isSelect() {
		return select;
	}

	public void setSelect(boolean select) {
		this.select = select;
	}

	public Long getCodigoColigada() {
		return codigoColigada;
	}

	public void setCodigoColigada(Long codigoColigada) {
		this.codigoColigada = codigoColigada;
	}

	public Long getCodigoSienge() {
		return codigoSienge;
	}

	public void setCodigoSienge(Long codigoSienge) {
		this.codigoSienge = codigoSienge;
	}

	public String getCodigoDepto() {
		return codigoDepto;
	}

	public void setCodigoDepto(String codigoDepto) {
		this.codigoDepto = codigoDepto;
	}

	public List<Usuario> getListaUsuarios() {
		return listaUsuarios;
	}

	public void setListaUsuarios(List<Usuario> listaUsuarios) {
		this.listaUsuarios = listaUsuarios;
	}
}
